home
***
CD-ROM
|
disk
|
FTP
|
other
***
search
/
Almathera Ten Pack 2: CDPD 1
/
Almathera Ten on Ten - Disc 2: CDPD 1.iso
/
pd
/
276-300
/
299
/
rxil
/
src
/
init.c
< prev
next >
Wrap
C/C++ Source or Header
|
1995-03-14
|
5KB
|
225 lines
/* init.c */
/* Copyright © 1989 by Donald T. Meyer, Stormgate Software
* All Rights Reserved
*/
#include "rxil.h"
#include <exec/memory.h>
#include <string.h>
static void unique_name( char portname[] );
struct RxsLib *RexxSysBase = NULL;
static char library_version_string[] = RXIL_VERSION_STRING;
/* NAME
* RxilInit
*
* SYNOPSIS
* rdef = RxilInit( flags, portname );
*
* struct RxilDef *rdef;
*
* ULONG flags;
* char *portname;
*
* FUNCTION
* Open the ARexx library and setup our message ports. Then
* allocate a RxilDef structure and do some default initialization
* of it.
* The portname will have a unique "instance" number appended
* to it in the format "<name>_#<n>" where <name> is the string as
* specified in the portname argument, and <n> is a decimal number
* from 1-99 inclusive. This feature may be inhibited by setting
* the RXIL_AS_IS flag.
*
* Even though this may fail, that should probably not be fatal
* since the ARexx functionality is optional. The RxilCheckPort()
* function is smart enough to just return if the rexx initialization
* was not successsfull. Not to mention that RxilCheckPort() should
* never get called since the rexx_sig_bit mask should be zero.
*
* INPUTS
* flags These are various defined constants which control
* which ports get opened and other various aspects
* of port initialization.
*
* portname This is the name to use for the public ARexx port
* that commands will be received at. It is suggested
* that this be in uppercase and contain no spaces.
* Maximum length is 40 characters, as set by the
* defined constant RXIL_MAX_PORTNAME_LEN.
* See discussion above about instance numbers.
*
* RESULT
* A pointer to a RxilDef structure. Return is NULL for failure
* to initialize the ARexx ports.
*
* SIDES
*
* HISTORY
* 01-Aug-89 Creation.
* 23-Sep-89 Changed "flags" arg from int to ULONG
* 26-Sep-89 Sets the (new) version string pointer.
* 01-Oct-89 Changed PublicPort name storage from a pointer to
* a character array. Added "instance" numbering.
* Added check on portname length.
*
* BUGS
* This should probably share one signal bit between both ports
* to avoid "hogging" signal bits.
*
* SEE ALSO
* RxilCleanup(), RXIL_AS_IS, RXIL_MAX_PORTNAME_LEN
*/
struct RxilDef *RxilInit( ULONG flags, char *portname )
{
char buf[24];
struct RxilDef *rdef;
if( ( strlen(portname) < 1 ) ||
( strlen(portname) > RXIL_MAX_PORTNAME_LEN ) )
{
/* Portname is of an invalid length */
return( NULL );
}
rdef = AllocMem( sizeof(struct RxilDef), MEMF_PUBLIC | MEMF_CLEAR );
if( rdef == NULL )
{
return( NULL );
}
/* Default initialization of the new RxilDef structure */
rdef->Console = NULL;
rdef->Extension = "rexx";
rdef->HostPort = "REXX";
strcpy( rdef->PortName, portname );
if( FlagIsClear( flags, RXIL_AS_IS ) )
{
/* Make sure the public port name is unique */
unique_name( rdef->PortName );
}
/* Open Rexx library */
RexxSysBase = (struct RxsLib *)OpenLibrary( RXSNAME, 0L );
if( RexxSysBase == NULL )
{
FreeMem( rdef, sizeof(struct RxilDef) );
return( NULL );
}
if( FlagIsSet( flags, RXIL_PUBLIC ) )
{
/* Setup our public port */
rdef->PublicPort = CreatePort( rdef->PortName, 1L );
if( rdef->PublicPort == NULL )
{
CloseLibrary( (struct Library *)RexxSysBase );
RexxSysBase = NULL;
FreeMem( rdef, sizeof(struct RxilDef) );
return( NULL );
}
rdef->SigBit |= 1L << (rdef->PublicPort->mp_SigBit);
}
if( FlagIsSet( flags, RXIL_SECRET ) )
{
/* Setup our secret port */
strcpy( rdef->SecretPortName, rdef->PortName );
strcat( rdef->SecretPortName, "_PRIVATE_" );
stcul_d( buf, (long)FindTask(NULL) );
strcat( rdef->SecretPortName, buf );
rdef->SecretPort = CreatePort( rdef->SecretPortName, 1L );
if( rdef->SecretPort == NULL )
{
/* Failure */
if( rdef->PublicPort )
{
RxilDeletePort( rdef->PublicPort );
rdef->PublicPort = NULL;
}
CloseLibrary( (struct Library *)RexxSysBase );
RexxSysBase = NULL;
rdef->SigBit = 0;
FreeMem( rdef, sizeof(struct RxilDef) );
return( NULL );
}
rdef->SigBit |= 1L << (rdef->SecretPort->mp_SigBit);
}
/* Set the version string pointer. */
rdef->Version = &library_version_string[0];
return( rdef );
}
/*
* This will take the port name in the buffer, and add a sequential
* invocation number to it to insure uniqueness.
*
* Note that this will increase the length of the given string!
* Make sure that the buffer is at least 4 characters longer than
* the original string.
*/
static void unique_name( char portname[] )
{
char buf[RXIL_MAX_PORTNAME_LEN+10], buf2[4];
unsigned int i;
for( i=1; i<100; i++ )
{
strcpy( buf, portname ); /* Orig. name "APP" (example) */
strcat( buf, "_#" ); /* "APP_#" */
stcu_d( buf2, i );
strcat( buf, buf2 ); /* "APP_#1" */
if( FindPort( buf ) == NULL )
{
/* Okay, this name does not exist. Let's use it. */
strcpy( portname, buf );
return;
}
}
/* Amazing! If we actually get here, there are already 99 instances
* of this program running. I cannot imagine ever getting here. :-)
* If we do, then I guess we'll just collide...
*/
}